package commons

import (
	"errors"
	"fmt"
	"one-wiki/database"
	"strconv"
	"strings"
	"time"
)

// 会话管理器实例 初始化时加载
var sessionManager SessionManager

// session过期时间 初始化时候加载
var sessionEffectiveTime int64
var duration time.Duration

// TODO
func init() {
	println("SessionManager Init ...")
	sessionEffectiveTime = 60
	sessionManager = DefaultSessionManager{}

	var err error
	duration, err = time.ParseDuration(fmt.Sprintf("%dm", sessionEffectiveTime))
	if err != nil {
		println("SessionManager Init Failed!!")
		panic(err)
	}
	println("SessionManager Inited!!")
}

// Session 会话信息
type Session struct {
	ID     string
	UserID int64
	Groups []int64
}

func AddSession(session Session) (err error) {
	return sessionManager.Add(session)
}

func GetSession(sessionID string) (Session, error) {
	return sessionManager.Get(sessionID)
}

func (s Session) IsAdmin() bool {
	for _, group := range s.Groups {
		if group == GROUP_ADMIN {
			return true
		}
	}
	return false
}

// SessionManager 会话管理器接口
type SessionManager interface {
	// Add 添加新的会话信息，返回新的会话ID
	Add(session Session) (err error)
	// Delete 删除指定会话信息
	Delete(sessionID string) error
	// Get 获取指定会话信息
	Get(sessionID string) (Session, error)
	// Update 设置指定会话信息，仅更新已存在的字段
	Update(sessionID string, session Session) error
}

type DefaultSessionManager struct {
}

func (d DefaultSessionManager) Add(session Session) (err error) {
	strSlice := make([]string, len(session.Groups))
	for i, item := range session.Groups {
		strSlice[i] = strconv.FormatInt(item, 10)
	}
	str := strings.Join(strSlice, ",")
	dbSession := database.Session{
		ID:             session.ID,
		UserID:         session.UserID,
		Groups:         str,
		CreateTime:     time.Now(),
		ExpirationTime: time.Now().Add(duration),
	}
	err = database.CreateSession(&dbSession)
	return err
}

func (d DefaultSessionManager) Delete(sessionID string) error {
	err := database.DeleteSessionByID(sessionID)
	return err
}

func (d DefaultSessionManager) Get(sessionID string) (Session, error) {
	res := Session{Groups: []int64{-1}}

	// 检查持久会话
	session, err := database.GetSessionByID(sessionID)
	if err != nil {
		return Session{}, err
	}

	// 如果会话不存在或已过期
	if session.ExpirationTime.Before(time.Now()) {
		return Session{}, errors.New("会话过期")
	}

	// 按照逗号分隔字符串并转换成整数切片
	groupList := strings.Split(session.Groups, ",")
	var groupIdList []int64
	for _, numStr := range groupList {
		num, err := strconv.Atoi(numStr)
		if err != nil {
			panic(err)
		}
		groupIdList = append(groupIdList, int64(num))
	}
	res.ID = session.ID
	res.UserID = session.UserID
	res.Groups = groupIdList
	return res, nil
}

func (d DefaultSessionManager) Update(sessionID string, session Session) error {
	//TODO implement me
	panic("implement me")
}
